-
Notifications
You must be signed in to change notification settings - Fork 118
FIXES: Fix authentication, repo-stats API, and Discord bot startup issues #239
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: main
Are you sure you want to change the base?
Conversation
|
Warning Rate limit exceeded
⌛ How to resolve this issue?After the wait time has elapsed, a review can be triggered using the We recommend that you space out your commits to avoid hitting the rate limit. 🚦 How do rate limits work?CodeRabbit enforces hourly rate limits for each developer per organization. Our paid plans have higher rate limits than the trial, open-source and free plans. In all cases, we re-allow further reviews after a brief timeout. Please see our FAQ for further information. 📒 Files selected for processing (1)
📝 WalkthroughWalkthroughFixes Supabase auth coroutine by awaiting token verification, adds a POST /repo-stats endpoint that fetches GitHub repo metadata, registers the legacy router under /api, adjusts Discord cog lifecycle to avoid cancelling idle cleanup tasks, and bumps the discord.py dependency range. Changes
Sequence Diagram(s)sequenceDiagram
participant Client as Frontend Client
participant API as Backend /repo-stats
participant GitHub as GitHub REST API
Client->>API: POST /api/repo-stats { repo_url }
activate API
API->>API: Parse owner/repo\nValidate URL and GitHub token
alt valid
API->>GitHub: GET /repos/{owner}/{repo} (Authorization)
activate GitHub
GitHub-->>API: 200 OK + repo metadata
deactivate GitHub
API->>API: Extract fields (name, stars, forks, owner, etc.)
API-->>Client: 200 OK + structured repo data
else invalid or error
API-->>Client: 400/401/500 Error
end
deactivate API
Estimated code review effort🎯 3 (Moderate) | ⏱️ ~25 minutes Possibly related PRs
Suggested reviewers
Poem
🚥 Pre-merge checks | ✅ 3 | ❌ 2❌ Failed checks (1 warning, 1 inconclusive)
✅ Passed checks (3 passed)
✏️ Tip: You can configure your own custom pre-merge checks in the settings. Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 3
🤖 Fix all issues with AI agents
In `@backend/routes.py`:
- Around line 54-58: Before building the GitHub API request headers in
backend/routes.py, validate that settings.github_token is set (non-empty) and
handle the missing token like in backend/app/services/github/user/profiling.py:
check settings.github_token, and if absent raise or return a clear error (or log
and abort the request) with an explanatory message about the missing GitHub
token so you don’t construct an invalid Authorization header; update the code
path that constructs headers = {"Authorization": f"token
{settings.github_token}", ...} to only run after this validation.
- Around line 46-52: The repo_url parsing is brittle; update the logic around
request.repo_url (and the variables repo_url, parts, owner, repo) to normalize
and robustly handle SSH URLs, URLs without protocol, and .git suffixes: first
trim whitespace, handle SSH format starting with "git@" by splitting on ":" to
get the path, otherwise ensure a scheme (prepend "https://" if missing) and use
a URL parser to get the path, strip leading/trailing slashes and any trailing
".git", split the path into segments, validate there are at least two segments,
then assign owner = segments[0] and repo = segments[1]; raise the same
HTTPException on invalid inputs.
🧹 Nitpick comments (2)
backend/integrations/discord/cogs.py (1)
43-45: Consider usinglogger.debug()instead ofprint()for consistency.The file uses
loggerelsewhere (e.g., line 47). Usingprint()for tracing bypasses log configuration (levels, formatting, handlers) and may clutter stdout in production.♻️ Suggested refactor
async def cleanup_expired_tokens(self): """Periodic cleanup of expired verification tokens""" try: - print("--> Running token cleanup task...") + logger.debug("Running token cleanup task...") await cleanup_expired_tokens() - print("--> Token cleanup task finished.") + logger.debug("Token cleanup task finished.") except Exception as e: logger.error(f"Error during token cleanup: {e}") `@cleanup_expired_tokens.before_loop` async def before_cleanup(self): """Wait until the bot is ready before starting cleanup""" - print("--> Waiting for bot to be ready before starting cleanup task...") + logger.debug("Waiting for bot to be ready before starting cleanup task...") await self.bot.wait_until_ready() - print("--> Bot is ready, starting cleanup task...") + logger.debug("Bot is ready, starting cleanup task...")Also applies to: 52-54
backend/routes.py (1)
91-95: Improve exception handling per best practices.The static analysis hints are valid here. Consider:
- Using
logging.exceptionto capture stack traces- Using
raise ... from efor exception chaining- Avoiding exposing internal error details to clients
♻️ Suggested improvement
except HTTPException: raise except Exception as e: - logging.error(f"Error fetching repo stats: {e}") - raise HTTPException(status_code=500, detail=str(e)) + logging.exception("Error fetching repo stats") + raise HTTPException(status_code=500, detail="Failed to fetch repository statistics") from e
📜 Review details
Configuration used: defaults
Review profile: CHILL
Plan: Pro
⛔ Files ignored due to path filters (2)
frontend/package-lock.jsonis excluded by!**/package-lock.jsonpoetry.lockis excluded by!**/*.lock
📒 Files selected for processing (5)
backend/app/core/dependencies.pybackend/integrations/discord/cogs.pybackend/main.pybackend/routes.pypyproject.toml
🧰 Additional context used
🧬 Code graph analysis (1)
backend/integrations/discord/cogs.py (1)
backend/app/core/orchestration/queue_manager.py (1)
start(47-56)
🪛 Ruff (0.14.11)
backend/routes.py
50-50: Abstract raise to an inner function
(TRY301)
68-71: Abstract raise to an inner function
(TRY301)
93-93: Do not catch blind exception: Exception
(BLE001)
94-94: Use logging.exception instead of logging.error
Replace with exception
(TRY400)
95-95: Within an except clause, raise exceptions with raise ... from err or raise ... from None to distinguish them from errors in exception handling
(B904)
🔇 Additional comments (4)
backend/integrations/discord/cogs.py (1)
35-37: LGTM! Good defensive check before cancellation.Checking
is_running()before callingcancel()prevents potential errors when the task hasn't started or has already completed.pyproject.toml (1)
11-11: Remove unusedpy-corddependency.Both
py-cordanddiscord-pyare listed inpyproject.toml(lines 11 and 29), but the codebase only imports fromdiscord(discord.py). Thepy-corddependency is unused and should be removed to avoid unnecessary bloat and potential namespace conflicts.backend/app/core/dependencies.py (1)
47-59: LGTM! Correct fix for the async authentication bug.The
awaitkeyword properly resolves the coroutine before accessinguser_response.user, fixing the "coroutine object has no attribute 'user'" error. Theget_supabase_client()function returns anAsyncClientinstance, andsupabase.auth.get_user(token)is correctly awaited. Error handling is well-structured.backend/main.py (1)
17-17: Router registration is correct with no route conflicts.The legacy router is properly imported and registered with the
/apiprefix. Routes are cleanly separated: legacy endpoints at/api/repo-statsand/api/github/webhook, while the main API routes remain under/v1/*.
✏️ Tip: You can disable this entire section by setting review_details to false in your review settings.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 1
🤖 Fix all issues with AI agents
In `@backend/routes.py`:
- Around line 124-128: The generic exception handler leaks internal details and
doesn't preserve traceback; replace the current block so that you call
logging.exception(...) to log the error with its traceback, return a generic
client-facing message (e.g., "Internal server error") instead of str(e) when
raising HTTPException, and re-raise using exception chaining (raise
HTTPException(status_code=500, detail="Internal server error") from e) so the
original exception context is preserved; update the except Exception as e: block
in backend/routes.py accordingly.
🧹 Nitpick comments (2)
backend/routes.py (2)
62-69: Unreachable exception handler.The
except (IndexError, ValueError)block at lines 68-69 is dead code. Since line 64 already checksif "github.com/" in repo_url, thesplit("github.com/", 1)[1]on line 65 will always succeed and return a string (never raiseIndexErrororValueError).♻️ Suggested simplification
# Extract path from URL - try: - # Parse URL to get path component - if "github.com/" in repo_url: - path = repo_url.split("github.com/", 1)[1] - else: - raise HTTPException(status_code=400, detail="Invalid GitHub repository URL") - except (IndexError, ValueError): + # Parse URL to get path component + if "github.com/" in repo_url: + path = repo_url.split("github.com/", 1)[1] + else: raise HTTPException(status_code=400, detail="Invalid GitHub repository URL")
79-97: Fix inconsistent indentation on comment lines.Lines 80 and 86 have extra leading whitespace before the comments, causing misalignment with the surrounding code. This appears to be a formatting error.
♻️ Suggested fix
owner, repo = segments[0], segments[1] - # Validate GitHub token is configured + + # Validate GitHub token is configured if not settings.github_token: raise HTTPException( status_code=500, detail="GitHub token not configured in environment variables. Please set GITHUB_TOKEN." ) - # Fetch repository stats from GitHub API + + # Fetch repository stats from GitHub API headers = {
📜 Review details
Configuration used: defaults
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (1)
backend/routes.py
🧰 Additional context used
🪛 Ruff (0.14.11)
backend/routes.py
55-55: Abstract raise to an inner function
(TRY301)
69-69: Within an except clause, raise exceptions with raise ... from err or raise ... from None to distinguish them from errors in exception handling
(B904)
77-77: Abstract raise to an inner function
(TRY301)
82-85: Abstract raise to an inner function
(TRY301)
101-104: Abstract raise to an inner function
(TRY301)
126-126: Do not catch blind exception: Exception
(BLE001)
127-127: Use logging.exception instead of logging.error
Replace with exception
(TRY400)
128-128: Within an except clause, raise exceptions with raise ... from err or raise ... from None to distinguish them from errors in exception handling
(B904)
🔇 Additional comments (3)
backend/routes.py (3)
10-11: LGTM!The imports for
settingsandhttpxare appropriate for the new repo-stats endpoint functionality.
15-16: LGTM!The
RepoRequestmodel is simple and sufficient. URL validation is handled in the endpoint logic.
99-123: LGTM!The error handling now logs the full error details server-side while returning a sanitized message to clients, addressing the previous concern about exposing raw GitHub API responses. The response structure is well-organized.
✏️ Tip: You can disable this entire section by setting review_details to false in your review settings.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 1
🤖 Fix all issues with AI agents
In `@backend/routes.py`:
- Around line 68-69: The except block catching IndexError/ValueError should
preserve the original exception context: change it to "except (IndexError,
ValueError) as e:" and re-raise the HTTPException using exception chaining
(e.g., "raise HTTPException(status_code=400, detail='Invalid GitHub repository
URL') from e") so the original error is retained for debugging while still
returning the HTTPException to callers.
📜 Review details
Configuration used: defaults
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (1)
backend/routes.py
🧰 Additional context used
🪛 Ruff (0.14.11)
backend/routes.py
55-55: Abstract raise to an inner function
(TRY301)
69-69: Within an except clause, raise exceptions with raise ... from err or raise ... from None to distinguish them from errors in exception handling
(B904)
77-77: Abstract raise to an inner function
(TRY301)
82-85: Abstract raise to an inner function
(TRY301)
101-104: Abstract raise to an inner function
(TRY301)
🔇 Additional comments (4)
backend/routes.py (4)
10-11: LGTM!Appropriate imports for the new functionality -
settingsfor configuration access andhttpxfor async HTTP requests.
15-16: LGTM!Simple and functional request model. URL validation is handled in the endpoint logic.
80-104: LGTM - Token validation and API error handling are well implemented.Good practices applied:
- Token validation before making the API request
- Error details logged server-side while returning a sanitized message to the client
- Reasonable timeout configured for the external call
Minor cosmetic note: Lines 80 and 86 have inconsistent comment indentation.
106-128: LGTM - Response structure and exception handling are well implemented.The response returns a clean, structured subset of repository data. The exception handling correctly:
- Re-raises
HTTPExceptionwithout modification- Uses
logging.exceptionfor automatic traceback inclusion- Returns a generic error message to clients
- Preserves exception context with
from e
✏️ Tip: You can disable this entire section by setting review_details to false in your review settings.
Closes #238
📝 Description
This PR fixes several bugs that prevented the application from running properly.
What was broken:
Authentication wasn't working
Users could not log in to the website because the code was attempting to access
useron a coroutine object instead of awaiting it first, resulting in authentication failures.Repo stats endpoint was missing
The
/api/repo-statsendpoint was defined inroutes.pybut was not registered with the main FastAPI application, causing the endpoint to return a 404 response.Discord bot crashed on startup
The Discord bot attempted to run a cleanup task before the bot was fully initialized, which caused a runtime error during startup.
🔧 Changes Made
What I fixed:
File: dependencies.py
Added
awaitbeforesupabase.auth.get_user(token)so the async call completes before accessing the user object.File: main.py
Imported the legacy router from
routes.pyand registered it with the FastAPI app usingapi.include_router(legacy_router, prefix="/api").This makes the repo stats endpoint available at
/api/repo-stats.File: routes.py
Added the missing
/repo-statsPOST endpoint implementation.The endpoint uses
httpxto call the GitHub API, fetches repository data (stars, forks, issues, etc.), parses the repository URL, and returns structured JSON.File: cogs.py
Improved the cleanup task to wait until the Discord bot is fully ready before running.
Added logging to indicate when the task is waiting versus running.
Fixed the
cog_unloadmethod to check whether the task is running before attempting to cancel it.Testing:
/api/repo-statsendpoint returns valid GitHub repository data.✅ Checklist
Summary by CodeRabbit
New Features
Bug Fixes
Chores
✏️ Tip: You can customize this high-level summary in your review settings.